package handlers

import (
	"fmt"
	"net/http"

	"github.com/gin-gonic/gin"
	"github.com/google/uuid"
	"github.com/sirupsen/logrus"
	"github.com/yourusername/virt-manager-go/internal/models"
	"github.com/yourusername/virt-manager-go/internal/service"
	"github.com/yourusername/virt-manager-go/internal/templates"
	libvirtlib "libvirt.org/go/libvirt"
)

// DomainHandler handles VM domain requests
type DomainHandler struct {
	connMgr *service.ConnectionManager
	log     *logrus.Logger
}

// NewDomainHandler creates a new domain handler
func NewDomainHandler(connMgr *service.ConnectionManager, log *logrus.Logger) *DomainHandler {
	return &DomainHandler{
		connMgr: connMgr,
		log:     log,
	}
}

// ListDomains returns all domains for a specific connection
//
//	@Summary		List domains
//	@Description	Returns all virtual machines for a specific connection
//	@Tags			domains
//	@Accept			json
//	@Produce		json
//	@Param			connection	query		string					false	"Connection ID"
//	@Param			inactive	query		bool					false	"Include inactive domains (default: true)"
//	@Success		200			{object}	map[string]interface{}	"{"domains": []models.DomainSummary, "count": int}"
//	@Failure		500			{object}	map[string]interface{}	"Internal Server Error"
//	@Router			/domains [get]
func (h *DomainHandler) ListDomains(c *gin.Context) {
	conn, err := getConnectionFromRequest(c, h.connMgr)
	if err != nil {
		h.log.WithError(err).Error("Failed to get connection")
		c.JSON(http.StatusInternalServerError, gin.H{"error": "connection not available"})
		return
	}

	// 获取inactive参数，默认为true（显示所有虚拟机）
	includeInactive := true
	if inactiveParam := c.Query("inactive"); inactiveParam != "" {
		if inactiveParam == "false" {
			includeInactive = false
		}
	}

	manager := service.NewDomainManager(conn)

	// 根据inactive参数决定列出哪些虚拟机
	var domains []libvirtlib.Domain
	if includeInactive {
		// 显示所有虚拟机（默认行为）
		domains, err = manager.ListAllDomains()
	} else {
		// 只显示活跃的虚拟机
		domains, err = manager.ListActiveDomains()
	}

	if err != nil {
		h.log.WithError(err).Error("Failed to list domains")
		c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
		return
	}

	result := make([]models.DomainSummary, 0, len(domains))
	for _, domain := range domains {
		name, _ := domain.GetName()
		uuid, _ := domain.GetUUIDString()
		state, _, _ := domain.GetState()
		info, _ := domain.GetInfo()

		active := false
		if state == libvirtlib.DOMAIN_RUNNING {
			active = true
		}

		result = append(result, models.DomainSummary{
			Name:   name,
			UUID:   uuid,
			State:  domainStateToString(state),
			Active: active,
			Memory: info.Memory,
			VCPUs:  info.NrVirtCpu,
		})

		if err := domain.Free(); err != nil {
			// 记录错误但继续执行
			h.log.WithError(err).Warn("Failed to free domain")
		}
	}

	c.JSON(http.StatusOK, gin.H{
		"domains": result,
		"count":   len(result),
	})
}

// GetDomain returns a specific domain
//
//	@Summary		Get domain details
//	@Description	Returns detailed information about a specific virtual machine
//	@Tags			domains
//	@Accept			json
//	@Produce		json
//	@Param			connection	query		string	true	"Connection ID"
//	@Param			name		query		string	true	"Domain name"
//	@Success		200			{object}	models.DomainDetail
//	@Failure		404			{object}	map[string]interface{}	"Domain not found"
//	@Failure		500			{object}	map[string]interface{}	"Internal Server Error"
//	@Router			/domain [get]
func (h *DomainHandler) GetDomain(c *gin.Context) {
	name := c.Query("name")
	if name == "" {
		c.JSON(http.StatusBadRequest, gin.H{"error": "name query parameter is required"})
		return
	}

	conn, err := getConnectionFromRequest(c, h.connMgr)
	if err != nil {
		c.JSON(http.StatusInternalServerError, gin.H{"error": "connection not available"})
		return
	}

	manager := service.NewDomainManager(conn)
	domain, err := manager.GetDomainByName(name)
	if err != nil {
		h.log.WithError(err).WithField("name", name).Error("Domain not found")
		c.JSON(http.StatusNotFound, gin.H{"error": "domain not found"})
		return
	}
	defer func() {
		if err := domain.Free(); err != nil {
			// 记录错误但继续执行
			h.log.WithError(err).Warn("Failed to free domain")
		}
	}()

	info, err := domain.GetInfo()
	if err != nil {
		h.log.WithError(err).Error("Failed to get domain info")
		c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
		return
	}

	uuid, _ := domain.GetUUIDString()
	state, _, _ := domain.GetState()
	xmlDesc, _ := domain.GetXMLDesc(0)

	c.JSON(http.StatusOK, models.DomainDetail{
		Name:      name,
		UUID:      uuid,
		State:     domainStateToString(state),
		Memory:    info.Memory,
		MaxMemory: info.MaxMem,
		VCPUs:     info.NrVirtCpu,
		CPUTime:   info.CpuTime,
		XMLConfig: xmlDesc,
	})
}

// CreateDomain creates a new domain
//
//	@Summary		Create domain
//	@Description	Creates a new virtual machine domain
//	@Tags			domains
//	@Accept			json
//	@Produce		json
//	@Param			connection	query		string						false	"Connection ID"
//	@Param			domain		body		models.CreateDomainRequest	true	"Domain configuration"
//	@Success		201			{object}	map[string]interface{}		"{"name": string, "uuid": string, "message": string}"
//	@Failure		400			{object}	map[string]interface{}		"Bad Request"
//	@Failure		500			{object}	map[string]interface{}		"Internal Server Error"
//	@Router			/domains [post]
func (h *DomainHandler) CreateDomain(c *gin.Context) {
	var req models.CreateDomainRequest
	if err := c.ShouldBindJSON(&req); err != nil {
		c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})
		return
	}

	// Validate request
	if req.Name == "" {
		c.JSON(http.StatusBadRequest, gin.H{"error": "name is required"})
		return
	}
	if req.DiskPath == "" {
		c.JSON(http.StatusBadRequest, gin.H{"error": "disk_path is required"})
		return
	}

	conn, err := getConnectionFromRequest(c, h.connMgr)
	if err != nil {
		c.JSON(http.StatusInternalServerError, gin.H{"error": "connection not available"})
		return
	}

	manager := service.NewDomainManager(conn)

	// Generate UUID if not provided
	if req.UUID == "" {
		req.UUID = uuid.New().String()
	}

	// Create domain XML from template
	builder := templates.NewBuilder()
	tmpl := &templates.DomainTemplate{
		Name:         req.Name,
		UUID:         req.UUID,
		Memory:       req.Memory,
		VCPUs:        req.VCPUs,
		Architecture: templates.Architecture(req.Architecture),
		BootMode:     templates.BootMode(req.BootMode),
		DiskPath:     req.DiskPath,
		DiskBus:      req.DiskBus,
		NetworkMode:  req.NetworkMode,
		NetworkName:  req.NetworkName,
		OSVariant:    req.OSVariant,
		SecureBoot:   req.SecureBoot,

		// CDROM configuration
		CDROMPath: req.CDROMPath,
		CDROMBus:  req.CDROMBus,
		CDROMBoot: req.CDROMBoot,
	}

	// Set defaults
	if tmpl.Memory == 0 {
		tmpl.Memory = 2048 // 2 GiB
	}
	if tmpl.VCPUs == 0 {
		tmpl.VCPUs = 2
	}
	if tmpl.Architecture == "" {
		tmpl.Architecture = templates.ArchX86_64
	}
	if tmpl.BootMode == "" {
		tmpl.BootMode = templates.BootModeBIOS
	}
	if tmpl.DiskBus == "" {
		tmpl.DiskBus = "virtio"
	}
	if tmpl.NetworkMode == "" {
		tmpl.NetworkMode = "network"
	}

	xmlConfig, err := builder.Build(tmpl)
	if err != nil {
		h.log.WithError(err).Error("Failed to build domain XML")
		c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})
		return
	}

	// Create domain
	domain, err := manager.CreateDomain(xmlConfig)
	if err != nil {
		h.log.WithError(err).Error("Failed to create domain")
		c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
		return
	}
	defer func() {
		if err := domain.Free(); err != nil {
			// 记录错误但继续执行
			h.log.WithError(err).Warn("Failed to free domain")
		}
	}()

	// Start domain if requested
	if req.AutoStart {
		if err := domain.Create(); err != nil {
			h.log.WithError(err).Warn("Failed to start domain")
		}
	}

	h.log.WithField("name", req.Name).Info("Domain created successfully")
	c.JSON(http.StatusCreated, gin.H{
		"name":    req.Name,
		"uuid":    req.UUID,
		"message": "domain created successfully",
	})
}

// DeleteDomain deletes a domain
//
//	@Summary		Delete domain
//	@Description	Deletes a virtual machine domain
//	@Tags			domains
//	@Accept			json
//	@Produce		json
//	@Param			connection	query		string					true	"Connection ID"
//	@Param			name		query		string					true	"Domain name"
//	@Success		200			{object}	map[string]interface{}	"{"message": string}"
//	@Failure		404			{object}	map[string]interface{}	"Domain not found"
//	@Failure		500			{object}	map[string]interface{}	"Internal Server Error"
//	@Router			/domain [delete]
func (h *DomainHandler) DeleteDomain(c *gin.Context) {
	name := c.Query("name")
	if name == "" {
		c.JSON(http.StatusBadRequest, gin.H{"error": "name query parameter is required"})
		return
	}

	conn, err := getConnectionFromRequest(c, h.connMgr)
	if err != nil {
		c.JSON(http.StatusInternalServerError, gin.H{"error": "connection not available"})
		return
	}

	manager := service.NewDomainManager(conn)
	if err := manager.DeleteDomain(name); err != nil {
		h.log.WithError(err).WithField("name", name).Error("Failed to delete domain")
		c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
		return
	}

	h.log.WithField("name", name).Info("Domain deleted successfully")
	c.JSON(http.StatusOK, gin.H{"message": "domain deleted successfully"})
}

// StartDomain starts a domain
//
//	@Summary		Start domain
//	@Description	Starts a virtual machine domain
//	@Tags			domains
//	@Accept			json
//	@Produce		json
//	@Param			connection	query		string					true	"Connection ID"
//	@Param			name		query		string					true	"Domain name"
//	@Success		200			{object}	map[string]interface{}	"{"message": string}"
//	@Failure		500			{object}	map[string]interface{}	"Internal Server Error"
//	@Router			/domain/start [post]
func (h *DomainHandler) StartDomain(c *gin.Context) {
	name := c.Query("name")
	if name == "" {
		c.JSON(http.StatusBadRequest, gin.H{"error": "name query parameter is required"})
		return
	}

	conn, err := getConnectionFromRequest(c, h.connMgr)
	if err != nil {
		c.JSON(http.StatusInternalServerError, gin.H{"error": "connection not available"})
		return
	}

	manager := service.NewDomainManager(conn)
	if err := manager.StartDomain(name); err != nil {
		h.log.WithError(err).WithField("name", name).Error("Failed to start domain")
		c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
		return
	}

	h.log.WithField("name", name).Info("Domain started successfully")
	c.JSON(http.StatusOK, gin.H{"message": "domain started successfully"})
}

// ShutdownDomain gracefully shuts down a domain
//
//	@Summary		Shutdown domain
//	@Description	Gracefully shuts down a virtual machine domain
//	@Tags			domains
//	@Accept			json
//	@Produce		json
//	@Param			connection	query		string					true	"Connection ID"
//	@Param			name		query		string					true	"Domain name"
//	@Success		200			{object}	map[string]interface{}	"{"message": string}"
//	@Failure		404			{object}	map[string]interface{}	"Domain not found"
//	@Failure		500			{object}	map[string]interface{}	"Internal Server Error"
//	@Router			/domain/shutdown [post]
func (h *DomainHandler) ShutdownDomain(c *gin.Context) {
	name := c.Query("name")
	if name == "" {
		c.JSON(http.StatusBadRequest, gin.H{"error": "name query parameter is required"})
		return
	}

	conn, err := getConnectionFromRequest(c, h.connMgr)
	if err != nil {
		c.JSON(http.StatusInternalServerError, gin.H{"error": "connection not available"})
		return
	}

	manager := service.NewDomainManager(conn)
	if err := manager.ShutdownDomain(name); err != nil {
		h.log.WithError(err).WithField("name", name).Error("Failed to shutdown domain")
		c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
		return
	}

	h.log.WithField("name", name).Info("Domain shutdown initiated")
	c.JSON(http.StatusOK, gin.H{"message": "domain shutdown initiated"})
}

// ForceStopDomain forcefully stops a domain
//
//	@Summary		Force stop domain
//	@Description	Forcefully stops a virtual machine domain
//	@Tags			domains
//	@Accept			json
//	@Produce		json
//	@Param			connection	query		string					true	"Connection ID"
//	@Param			name		query		string					true	"Domain name"
//	@Success		200			{object}	map[string]interface{}	"{"message": string}"
//	@Failure		404			{object}	map[string]interface{}	"Domain not found"
//	@Failure		500			{object}	map[string]interface{}	"Internal Server Error"
//	@Router			/domain/force-stop [post]
func (h *DomainHandler) ForceStopDomain(c *gin.Context) {
	name := c.Query("name")
	if name == "" {
		c.JSON(http.StatusBadRequest, gin.H{"error": "name query parameter is required"})
		return
	}

	conn, err := getConnectionFromRequest(c, h.connMgr)
	if err != nil {
		c.JSON(http.StatusInternalServerError, gin.H{"error": "connection not available"})
		return
	}

	manager := service.NewDomainManager(conn)
	if err := manager.ForceStopDomain(name); err != nil {
		h.log.WithError(err).WithField("name", name).Error("Failed to force stop domain")
		c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
		return
	}

	h.log.WithField("name", name).Info("Domain force stopped")
	c.JSON(http.StatusOK, gin.H{"message": "domain force stopped"})
}

// RebootDomain reboots a domain
//
//	@Summary		Reboot domain
//	@Description	Reboots a virtual machine domain
//	@Tags			domains
//	@Accept			json
//	@Produce		json
//	@Param			connection	query		string					true	"Connection ID"
//	@Param			name		query		string					true	"Domain name"
//	@Success		200			{object}	map[string]interface{}	"{"message": string}"
//	@Failure		404			{object}	map[string]interface{}	"Domain not found"
//	@Failure		500			{object}	map[string]interface{}	"Internal Server Error"
//	@Router			/domain/reboot [post]
func (h *DomainHandler) RebootDomain(c *gin.Context) {
	name := c.Query("name")
	if name == "" {
		c.JSON(http.StatusBadRequest, gin.H{"error": "name query parameter is required"})
		return
	}

	conn, err := getConnectionFromRequest(c, h.connMgr)
	if err != nil {
		c.JSON(http.StatusInternalServerError, gin.H{"error": "connection not available"})
		return
	}

	manager := service.NewDomainManager(conn)
	if err := manager.RebootDomain(name); err != nil {
		h.log.WithError(err).WithField("name", name).Error("Failed to reboot domain")
		c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
		return
	}

	h.log.WithField("name", name).Info("Domain rebooted")
	c.JSON(http.StatusOK, gin.H{"message": "domain rebooted"})
}

// SuspendDomain suspends a domain
//
//	@Summary		Suspend domain
//	@Description	Suspends a virtual machine domain
//	@Tags			domains
//	@Accept			json
//	@Produce		json
//	@Param			connection	query		string					true	"Connection ID"
//	@Param			name		query		string					true	"Domain name"
//	@Success		200			{object}	map[string]interface{}	"{"message": string}"
//	@Failure		404			{object}	map[string]interface{}	"Domain not found"
//	@Failure		500			{object}	map[string]interface{}	"Internal Server Error"
//	@Router			/domain/suspend [post]
func (h *DomainHandler) SuspendDomain(c *gin.Context) {
	name := c.Query("name")
	if name == "" {
		c.JSON(http.StatusBadRequest, gin.H{"error": "name query parameter is required"})
		return
	}

	conn, err := getConnectionFromRequest(c, h.connMgr)
	if err != nil {
		c.JSON(http.StatusInternalServerError, gin.H{"error": "connection not available"})
		return
	}

	manager := service.NewDomainManager(conn)
	domain, err := manager.GetDomainByName(name)
	if err != nil {
		c.JSON(http.StatusNotFound, gin.H{"error": "domain not found"})
		return
	}
	defer func() {
		if err := domain.Free(); err != nil {
			// 记录错误但继续执行
			h.log.WithError(err).Warn("Failed to free domain")
		}
	}()

	if err := domain.Suspend(); err != nil {
		h.log.WithError(err).Error("Failed to suspend domain")
		c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
		return
	}

	c.JSON(http.StatusOK, gin.H{"message": "domain suspended"})
}

// ResumeDomain resumes a suspended domain
//
//	@Summary		Resume domain
//	@Description	Resumes a suspended virtual machine domain
//	@Tags			domains
//	@Accept			json
//	@Produce		json
//	@Param			connection	query		string					true	"Connection ID"
//	@Param			name		query		string					true	"Domain name"
//	@Success		200			{object}	map[string]interface{}	"{"message": string}"
//	@Failure		404			{object}	map[string]interface{}	"Domain not found"
//	@Failure		500			{object}	map[string]interface{}	"Internal Server Error"
//	@Router			/domain/resume [post]
func (h *DomainHandler) ResumeDomain(c *gin.Context) {
	name := c.Query("name")
	if name == "" {
		c.JSON(http.StatusBadRequest, gin.H{"error": "name query parameter is required"})
		return
	}

	conn, err := getConnectionFromRequest(c, h.connMgr)
	if err != nil {
		c.JSON(http.StatusInternalServerError, gin.H{"error": "connection not available"})
		return
	}

	manager := service.NewDomainManager(conn)
	domain, err := manager.GetDomainByName(name)
	if err != nil {
		c.JSON(http.StatusNotFound, gin.H{"error": "domain not found"})
		return
	}
	defer func() {
		if err := domain.Free(); err != nil {
			// 记录错误但继续执行
			h.log.WithError(err).Warn("Failed to free domain")
		}
	}()

	if err := domain.Resume(); err != nil {
		h.log.WithError(err).Error("Failed to resume domain")
		c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
		return
	}

	c.JSON(http.StatusOK, gin.H{"message": "domain resumed"})
}

// SetVCPUs sets the number of vCPUs
//
//	@Summary		Set domain vCPUs
//	@Description	Sets the number of vCPUs for a domain
//	@Tags			domains
//	@Accept			json
//	@Produce		json
//	@Param			connection	query		string					true	"Connection ID"
//	@Param			name		query		string					true	"Domain name"
//	@Param			vcpus		body		object					true	"vCPUs configuration"
//	@Success		200			{object}	map[string]interface{}	"{"message": string}"
//	@Failure		400			{object}	map[string]interface{}	"Bad Request"
//	@Failure		404			{object}	map[string]interface{}	"Domain not found"
//	@Failure		500			{object}	map[string]interface{}	"Internal Server Error"
//	@Router			/domain/vcpus [put]
func (h *DomainHandler) SetVCPUs(c *gin.Context) {
	name := c.Query("name")
	if name == "" {
		c.JSON(http.StatusBadRequest, gin.H{"error": "name query parameter is required"})
		return
	}

	var req struct {
		VCPUs uint `json:"vcpus" binding:"required,min=1"`
	}

	if err := c.ShouldBindJSON(&req); err != nil {
		c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})
		return
	}

	conn, err := getConnectionFromRequest(c, h.connMgr)
	if err != nil {
		c.JSON(http.StatusInternalServerError, gin.H{"error": "connection not available"})
		return
	}

	manager := service.NewDomainManager(conn)
	if err := manager.SetDomainVCPUs(name, req.VCPUs); err != nil {
		h.log.WithError(err).Error("Failed to set vCPUs")
		c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
		return
	}

	c.JSON(http.StatusOK, gin.H{"message": "vCPUs updated"})
}

// SetMemory sets domain memory
//
//	@Summary		Set domain memory
//	@Description	Sets memory for a domain
//	@Tags			domains
//	@Accept			json
//	@Produce		json
//	@Param			connection	query		string					true	"Connection ID"
//	@Param			name		query		string					true	"Domain name"
//	@Param			memory		body		object					true	"Memory configuration"
//	@Success		200			{object}	map[string]interface{}	"{"message": string}"
//	@Failure		400			{object}	map[string]interface{}	"Bad Request"
//	@Failure		404			{object}	map[string]interface{}	"Domain not found"
//	@Failure		500			{object}	map[string]interface{}	"Internal Server Error"
//	@Router			/domain/memory [put]
func (h *DomainHandler) SetMemory(c *gin.Context) {
	name := c.Query("name")
	if name == "" {
		c.JSON(http.StatusBadRequest, gin.H{"error": "name query parameter is required"})
		return
	}

	var req struct {
		Memory uint64 `json:"memory" binding:"required,min=512"` // KiB
	}

	if err := c.ShouldBindJSON(&req); err != nil {
		c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})
		return
	}

	conn, err := getConnectionFromRequest(c, h.connMgr)
	if err != nil {
		c.JSON(http.StatusInternalServerError, gin.H{"error": "connection not available"})
		return
	}

	manager := service.NewDomainManager(conn)
	if err := manager.SetDomainMemory(name, req.Memory); err != nil {
		h.log.WithError(err).Error("Failed to set memory")
		c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
		return
	}

	c.JSON(http.StatusOK, gin.H{"message": "memory updated"})
}

// GetDomainXML returns domain XML configuration
//
//	@Summary		Get domain XML
//	@Description	Returns domain XML configuration
//	@Tags			domains
//	@Accept			json
//	@Produce		xml
//	@Param			connection	query		string					true	"Connection ID"
//	@Param			name		query		string					true	"Domain name"
//	@Success		200			{string}	string					"XML configuration"
//	@Failure		404			{object}	map[string]interface{}	"Domain not found"
//	@Router			/domain/xml [get]
func (h *DomainHandler) GetDomainXML(c *gin.Context) {
	name := c.Query("name")
	if name == "" {
		c.JSON(http.StatusBadRequest, gin.H{"error": "name query parameter is required"})
		return
	}

	conn, err := getConnectionFromRequest(c, h.connMgr)
	if err != nil {
		c.JSON(http.StatusInternalServerError, gin.H{"error": "connection not available"})
		return
	}

	manager := service.NewDomainManager(conn)
	xmlDesc, err := manager.GetDomainXML(name)
	if err != nil {
		c.JSON(http.StatusNotFound, gin.H{"error": "domain not found"})
		return
	}

	c.Data(http.StatusOK, "application/xml", []byte(xmlDesc))
}

// GetDomainStats returns domain statistics
//
//	@Summary		Get domain statistics
//	@Description	Returns domain statistics
//	@Tags			domains
//	@Accept			json
//	@Produce		json
//	@Param			connection	query		string					true	"Connection ID"
//	@Param			name		query		string					true	"Domain name"
//	@Success		200			{object}	map[string]interface{}	"Domain statistics"
//	@Failure		404			{object}	map[string]interface{}	"Domain not found"
//	@Router			/domain/stats [get]
func (h *DomainHandler) GetDomainStats(c *gin.Context) {
	name := c.Query("name")
	if name == "" {
		c.JSON(http.StatusBadRequest, gin.H{"error": "name query parameter is required"})
		return
	}

	conn, err := getConnectionFromRequest(c, h.connMgr)
	if err != nil {
		c.JSON(http.StatusInternalServerError, gin.H{"error": "connection not available"})
		return
	}

	manager := service.NewDomainManager(conn)
	info, err := manager.GetDomainInfo(name)
	if err != nil {
		c.JSON(http.StatusNotFound, gin.H{"error": "domain not found"})
		return
	}

	c.JSON(http.StatusOK, gin.H{
		"memory":     info.Memory,
		"max_memory": info.MaxMem,
		"vcpus":      info.NrVirtCpu,
		"cpu_time":   info.CpuTime,
		"state":      domainStateToString(info.State),
	})
}

// GetDomainStatus returns simplified domain status
//
//	@Summary		Get domain status
//	@Description	Returns simplified domain status
//	@Tags			domains
//	@Accept			json
//	@Produce		json
//	@Param			connection	query		string					true	"Connection ID"
//	@Param			name		query		string					true	"Domain name"
//	@Success		200			{object}	map[string]interface{}	"Domain status"
//	@Failure		404			{object}	map[string]interface{}	"Domain not found"
//	@Router			/domain/status [get]
func (h *DomainHandler) GetDomainStatus(c *gin.Context) {
	name := c.Query("name")
	if name == "" {
		c.JSON(http.StatusBadRequest, gin.H{"error": "name query parameter is required"})
		return
	}

	conn, err := getConnectionFromRequest(c, h.connMgr)
	if err != nil {
		c.JSON(http.StatusInternalServerError, gin.H{"error": "connection not available"})
		return
	}

	manager := service.NewDomainManager(conn)
	domain, err := manager.GetDomainByName(name)
	if err != nil {
		c.JSON(http.StatusNotFound, gin.H{"error": "domain not found"})
		return
	}
	defer func() {
		if err := domain.Free(); err != nil {
			// 记录错误但继续执行
			h.log.WithError(err).Warn("Failed to free domain")
		}
	}()

	state, _, _ := domain.GetState()
	active, _ := domain.IsActive()

	c.JSON(http.StatusOK, gin.H{
		"name":   name,
		"state":  domainStateToString(state),
		"active": active,
	})
}

// GenerateFromTemplate generates domain XML from a template
//
//	@Summary		Generate domain XML from template
//	@Description	Generates and returns domain XML configuration based on provided template parameters
//	@Tags			domains
//	@Accept			json
//	@Produce		xml
//	@Param			template	body		models.CreateDomainRequest	true	"Domain template configuration"
//	@Success		200			{string}	string						"XML configuration"
//	@Failure		400			{object}	map[string]interface{}		"Bad Request"
//	@Failure		500			{object}	map[string]interface{}		"Internal Server Error"
//	@Router			/templates/generate [post]
func (h *DomainHandler) GenerateFromTemplate(c *gin.Context) {
	var req models.CreateDomainRequest
	if err := c.ShouldBindJSON(&req); err != nil {
		c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})
		return
	}

	builder := templates.NewBuilder()
	tmpl := &templates.DomainTemplate{
		Name:         req.Name,
		UUID:         req.UUID,
		Memory:       req.Memory,
		VCPUs:        req.VCPUs,
		Architecture: templates.Architecture(req.Architecture),
		BootMode:     templates.BootMode(req.BootMode),
		DiskPath:     req.DiskPath,
		DiskBus:      req.DiskBus,
		NetworkMode:  req.NetworkMode,
		NetworkName:  req.NetworkName,
		OSVariant:    req.OSVariant,
		SecureBoot:   req.SecureBoot,
	}

	xmlConfig, err := builder.Build(tmpl)
	if err != nil {
		c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})
		return
	}

	c.Data(http.StatusOK, "application/xml", []byte(xmlConfig))
}

// Helper function to convert domain state to string
func domainStateToString(state libvirtlib.DomainState) string {
	states := map[libvirtlib.DomainState]string{
		libvirtlib.DOMAIN_NOSTATE:     "no state",
		libvirtlib.DOMAIN_RUNNING:     "running",
		libvirtlib.DOMAIN_BLOCKED:     "blocked",
		libvirtlib.DOMAIN_PAUSED:      "paused",
		libvirtlib.DOMAIN_SHUTDOWN:    "shutdown",
		libvirtlib.DOMAIN_SHUTOFF:     "shut off",
		libvirtlib.DOMAIN_CRASHED:     "crashed",
		libvirtlib.DOMAIN_PMSUSPENDED: "suspended",
	}

	if str, ok := states[state]; ok {
		return str
	}
	return fmt.Sprintf("unknown (%d)", state)
}
